package com.cly.config;

import com.baomidou.mybatisplus.annotation.FieldFill;
import com.baomidou.mybatisplus.core.toolkit.IdWorker;
import com.cly.properties.MyBatisObjectFillProperties;
import com.cly.result.exception.ServiceException;
import com.cly.result.exenum.RequestException;
import com.cly.utils.BaseContext;
import lombok.extern.slf4j.Slf4j;
import org.apache.ibatis.reflection.MetaObject;
import org.springframework.util.ReflectionUtils;

import java.lang.reflect.Method;

/**
 * 自定义基于配置的填充策略
 *
 * @author 春风能解释
 * <p>
 * 2024-6-30
 */
// @Component
@Slf4j
@Deprecated
public class MyMetaObjectHandler2
        // implements MetaObjectHandler
{

    /**
     * 自动填充策略配置
     */
    // @Resource
    private MyBatisObjectFillProperties myBatisObjectFillProperties;

    /**
     * 数据添加是: 自动填充策略
     *
     * @param metaObject 参数对象
     */
    // @Override
    public void insertFill(MetaObject metaObject) {
        autoFill(metaObject, FieldFill.INSERT);
    }

    /**
     * 数据修改时填充策略
     *
     * @param metaObject 参数对象
     */
    // @Override
    public void updateFill(MetaObject metaObject) {
        autoFill(metaObject, FieldFill.INSERT_UPDATE);
    }

    /**
     * 根据策略填充属性值
     *
     * @param metaObject 参数对象
     * @param fieldFill  填充策略
     */
    public void autoFill(MetaObject metaObject, FieldFill fieldFill) {
        String methodName =
                fieldFill.equals(FieldFill.INSERT) ?
                        "strictInsertFill" : // 新增填充
                        "strictUpdateFill"; // 修改填充
        log.info("开始自动填充策略:{}", methodName);
        // 获取方法
        Method method = ReflectionUtils.findMethod(
                this.getClass(),
                methodName,
                //////////////////参数列表//////////////////
                MetaObject.class,
                String.class,
                Class.class,
                Object.class);
        if (method == null) {
            throw new ServiceException(RequestException.UNKNOWN_EXCEPTION);
        }
        // 遍历属性
        myBatisObjectFillProperties.getFileMap()
                .forEach(myBatisFillObject -> {
                    // 根据策略类型
                    switch (myBatisFillObject.getType()) {
                        // ID填充策略
                        case ID -> {
                            ReflectionUtils.invokeMethod(method,
                                    this,
                                    //////////////////参数列表//////////////////
                                    // 新增填充：this.strictInsertFill(metaObject, myBatisFillObject.getProperty(), Long.class, IdWorker.getId());
                                    // 修改填充：this.strictUpdateFill(metaObject, myBatisFillObject.getProperty(), Long.class, IdWorker.getId());
                                    metaObject,
                                    myBatisFillObject.getProperty(),
                                    Long.class,
                                    IdWorker.getId());
                            log.info("ID填充策略填充成功");
                        }
                        case USER -> {
                            ReflectionUtils.invokeMethod(method,
                                    this,
                                    //////////////////参数列表//////////////////
                                    // 新增填充：this.strictInsertFill(metaObject, myBatisFillObject.getProperty(), Long.class, BaseContext.getCurrentId());
                                    // 修改填充：this.strictUpdateFill(metaObject, myBatisFillObject.getProperty(), Long.class, BaseContext.getCurrentId());
                                    metaObject,
                                    myBatisFillObject.getProperty(),
                                    Long.class,
                                    BaseContext.getCurrentId());
                            log.info("用户填充策略填充成功");
                            // 日期填充策略
                        }
                        default -> {
                            ReflectionUtils.invokeMethod(method,
                                    this,
                                    //////////////////参数列表//////////////////
                                    // 新增填充：this.strictInsertFill(metaObject, myBatisFillObject.getProperty(), String.class, BaseContext.date());
                                    // 修改填充：this.strictUpdateFill(metaObject, myBatisFillObject.getProperty(), String.class, BaseContext.date());
                                    metaObject,
                                    myBatisFillObject.getProperty(),
                                    String.class,
                                    BaseContext.date());
                            log.info("日期填充策略填充成功");
                        }
                    }

                });

    }
}